#include "stdafx.h"
#include "FileCipher.h"
#include <fstream>
using namespace std;

void FileCipher::read_file(const char *const in_name,text *const t)
{
	int int_size=sizeof(uint);
	ifstream infile;
	infile.open(in_name,ios_base::binary);
	int flag;
	while(!infile.eof())
	{
		uint *f=new uint(0),*s=new uint(0);
		infile.read((char*)f,int_size);
		infile.read((char*)s,int_size);
		block b(*f,*s);
		t->push_back(b);
		flag=*f;
		delete f;
		delete s;
	}
	if(flag==0) t->pop_back();
	infile.close();
	//infile.read(reinterpret_cast<char *>(&s),size);
	//infile.rdbuf()->in_avail();
}
void FileCipher::write_file(const char *const out_name,const text *const res)
{
	ofstream outfile;
	outfile.open(out_name,ios_base::binary);
	for(ptext i=res->begin(); i<res->end()-1;++i)
	{
		uint f=i->l,s=i->r;
		outfile.write((char*)(&f),sizeof(uint));
		outfile.write((char*)(&s),sizeof(uint));
	}

	uint f=(res->end()-1)->l,s=(res->end()-1)->r;
	if(f!=0)
	{
		if(s==0)
		{
			outfile.write((char*)(&f),sizeof(uint));
		}
		else
		{
			outfile.write((char*)(&f),sizeof(uint));
			outfile.write((char*)(&s),sizeof(uint));
		}
	}

	outfile.close();
}
void FileCipher::Encipher(const char *const plain_file,const char *const enc_file, Block_Cipher *c,const MODE mode)
{
	text *t=new text;
	read_file(plain_file,t);
	text *res=c->Encipher(*t,mode);
	delete t;
	write_file(enc_file,res);	
}
void FileCipher::Decipher(const char *const enc_file,const char *const dec_file, Block_Cipher *c,const MODE mode)
{
	text *t=new text;
	read_file(enc_file,t);
	text *res=c->Decipher(*t,mode);
	delete t;
	write_file(dec_file,res);
}

init_vector FileCipher::Get_Hash(const char *const plain_file, Block_Cipher *c)
{
	text *t=new text;
	read_file(plain_file,t);
	init_vector i=c->Get_Hash(*t);
	delete t;
	return i;
}